import 'dart:io';

import 'package:image_crop_nic/image_crop_nic.dart';
import 'package:image_picker_plus_nic/image_picker_plus_nic.dart';
import 'package:image_picker_plus_nic/src/crop_image_view.dart';
import 'package:image_picker_plus_nic/src/custom_packages/crop_image/crop_image.dart';
import 'package:image_picker_plus_nic/src/dialog_widget.dart';
import 'package:image_picker_plus_nic/src/image.dart';
import 'package:image_picker_plus_nic/src/multi_selection_mode.dart';
import 'package:flutter/foundation.dart';
import 'package:flutter/material.dart';
import 'package:image_picker_plus_nic/src/preview_image_view.dart';
import 'package:image_picker_plus_nic/src/utilities/string_format_extension.dart';
import 'package:photo_manager/photo_manager.dart';
import 'package:shimmer/shimmer.dart';
import 'package:flutter_svg/flutter_svg.dart';
import 'package:badges/badges.dart' as badges;

// 圖片檢視頁
class ImagesViewPage extends StatefulWidget {
  final GalleryDisplaySettings? galleryDisplaySettings;
  final ValueNotifier<List<File>> multiSelectedImages;
  final ValueNotifier<bool> multiSelectionMode;
  final UiTexts uiTexts;
  final bool cropImage;
  final bool multiSelection;
  final bool showInternalVideos;
  final bool showInternalImages;
  final int maximumSelection;
  final int? selectIndex;

  /// To avoid lag when you interacting with image when it expanded
  final AppTheme appTheme;
  final VoidCallback clearMultiImages;
  final Color whiteColor;
  final Color blackColor;
  final Color primaryColor;
  final TextStyle textStyle;
  final bool showImagePreview;
  final bool showImageCrop;
  final SliverGridDelegateWithFixedCrossAxisCount gridDelegate;
  final void Function()? next;
  final void Function(DisplayMode m)? doChangeMode;

  const ImagesViewPage({
    Key? key,
    required this.galleryDisplaySettings,
    required this.multiSelectedImages,
    required this.multiSelectionMode,
    required this.clearMultiImages,
    required this.appTheme,
    required this.whiteColor,
    required this.cropImage,
    required this.multiSelection,
    required this.showInternalVideos,
    required this.showInternalImages,
    required this.blackColor,
    required this.showImagePreview,
    required this.showImageCrop,
    required this.gridDelegate,
    required this.maximumSelection,
    required this.uiTexts,
    required this.primaryColor,
    required this.textStyle,
    this.next,
    this.selectIndex,
    this.doChangeMode,
  }) : super(key: key);

  @override
  State<ImagesViewPage> createState() => _ImagesViewPageState();
}

class _ImagesViewPageState extends State<ImagesViewPage>
    with
        TickerProviderStateMixin,
        AutomaticKeepAliveClientMixin<ImagesViewPage> {
  final ValueNotifier<List<FutureBuilder<Uint8List?>>> _mediaList =
      ValueNotifier([]);

  ValueNotifier<List<File?>> allImages = ValueNotifier([]);
  final ValueNotifier<List<double?>> scaleOfCropsKeys = ValueNotifier([]);
  final ValueNotifier<List<Rect?>> areaOfCropsKeys = ValueNotifier([]);

  ValueNotifier<File?> selectedImage = ValueNotifier(null);

  int selectedIndex = -1;
  ValueNotifier<List<int>> indexOfSelectedImages = ValueNotifier([]);

  ScrollController scrollController = ScrollController();

  final expandImage = ValueNotifier(false);
  final expandHeight = ValueNotifier(0.0);
  final moveAwayHeight = ValueNotifier(0.0);
  final expandImageView = ValueNotifier(false);

  final isImagesReady = ValueNotifier(false);
  final isPreviewing = ValueNotifier(false); //預覽中
  final currentPage = ValueNotifier(0);
  final lastPage = ValueNotifier(0);

  /// To avoid lag when you interacting with image when it expanded
  final enableVerticalTapping = ValueNotifier(false);
  final cropKey = ValueNotifier(GlobalKey<CustomCropState>());
  bool noPaddingForGridView = false;

  double scrollPixels = 0.0;
  bool isScrolling = false;
  bool noImages = false;
  final noDuration = ValueNotifier(false);
  int indexOfLatestImage = -1;

  @override
  void dispose() {
    _mediaList.dispose();
    allImages.dispose();
    scrollController.dispose();
    isImagesReady.dispose();
    isPreviewing.dispose();
    currentPage.dispose();
    lastPage.dispose();
    expandImage.dispose();
    expandHeight.dispose();
    moveAwayHeight.dispose();
    expandImageView.dispose();
    enableVerticalTapping.dispose();
    cropKey.dispose();
    noDuration.dispose();
    selectedImage.dispose();
    scaleOfCropsKeys.dispose();
    areaOfCropsKeys.dispose();
    indexOfSelectedImages.dispose();
    super.dispose();
  }

  late Widget forBack;
  @override
  void initState() {
    _fetchNewMedia(currentPageValue: 0);
    super.initState();
    //設定為多選模式
    if (widget.multiSelection) {
      widget.multiSelectionMode.value = true;
    }
  }

  bool _handleScrollEvent(ScrollNotification scroll,
      {required int currentPageValue, required int lastPageValue}) {
    if (scroll.metrics.pixels / scroll.metrics.maxScrollExtent > 0.33 &&
        currentPageValue != lastPageValue) {
      _fetchNewMedia(currentPageValue: currentPageValue);
      return true;
    }
    return false;
  }

  // 抓取所有圖片來源
  _fetchNewMedia({required int currentPageValue}) async {
    //print('_fetchNewMedia()');
    lastPage.value = currentPageValue;
    PermissionState result = await PhotoManager.requestPermissionExtend();
    if (result.isAuth) {
      RequestType type = widget.showInternalVideos && widget.showInternalImages
          ? RequestType.common
          : (widget.showInternalImages ? RequestType.image : RequestType.video);

      List<AssetPathEntity> albums =
          await PhotoManager.getAssetPathList(onlyAll: true, type: type);
      if (albums.isEmpty) {
        WidgetsBinding.instance
            .addPostFrameCallback((_) => setState(() => noImages = true));
        return;
      } else if (noImages) {
        noImages = false;
      }
      List<AssetEntity> media =
          await albums[0].getAssetListPaged(page: currentPageValue, size: 60);
      List<FutureBuilder<Uint8List?>> temp = [];
      List<File?> imageTemp = [];

      for (int i = 0; i < media.length; i++) {
        FutureBuilder<Uint8List?> gridViewImage =
            await getImageGallery(media, i);
        File? image = await highQualityImage(media, i);
        temp.add(gridViewImage);
        imageTemp.add(image);
      }
      _mediaList.value.addAll(temp);
      allImages.value.addAll(imageTemp);
      if (widget.showImageCrop) {
        //裁切模式才需要預設值
        //print('widget.selectIndex=${widget.selectIndex}');
        if (widget.selectIndex != null &&
            widget.selectIndex! < allImages.value.length) {
          selectedImage.value = allImages.value[widget.selectIndex!];
          selectedIndex = widget.selectIndex!;
        } else {
          selectedImage.value = allImages.value[0];
          selectedIndex = 0;
        }
      }
      currentPage.value++;
      isImagesReady.value = true;
      WidgetsBinding.instance.addPostFrameCallback((_) => setState(() {}));
    } else {
      await PhotoManager.requestPermissionExtend();
      PhotoManager.openSetting();
    }
  }

  Future<FutureBuilder<Uint8List?>> getImageGallery(
      List<AssetEntity> media, int i) async {
    bool highResolution = widget.gridDelegate.crossAxisCount <= 3;
    FutureBuilder<Uint8List?> futureBuilder = FutureBuilder(
      future: media[i].thumbnailDataWithSize(highResolution
          ? const ThumbnailSize(350, 350)
          : const ThumbnailSize(200, 200)),
      builder: (BuildContext context, AsyncSnapshot<Uint8List?> snapshot) {
        if (snapshot.connectionState == ConnectionState.done) {
          Uint8List? image = snapshot.data;
          if (image != null) {
            return Container(
              color: const Color.fromARGB(255, 189, 189, 189),
              child: Stack(
                children: <Widget>[
                  Positioned.fill(
                    child: MemoryImageDisplay(
                        imageBytes: image, appTheme: widget.appTheme),
                  ),
                  if (media[i].type == AssetType.video)
                    const Align(
                      alignment: Alignment.bottomRight,
                      child: Padding(
                        padding: EdgeInsets.only(right: 5, bottom: 5),
                        child: Icon(
                          Icons.slow_motion_video_rounded,
                          color: Colors.white,
                        ),
                      ),
                    ),
                ],
              ),
            );
          }
        }
        return const SizedBox();
      },
    );
    return futureBuilder;
  }

  Future<File?> highQualityImage(List<AssetEntity> media, int i) async =>
      media[i].file;

  @override
  Widget build(BuildContext context) {
    super.build(context);
    return _buildView(context);
  }

  Widget _buildTitle(BuildContext context) {
    return SizedBox(
      height: 54,
      width: MediaQuery.of(context).size.width,
      child: ListTile(
        leading: widget.showImageCrop == true || isPreviewing.value == true
            ? InkWell(
                child: SvgPicture.asset(
                  'packages/image_picker_plus_nic/assets/back.svg',
                  width: 24,
                  height: 24,
                  color:
                      isPreviewing.value == true ? Colors.white : Colors.black,
                ),
                onTap: () {
                  if (isPreviewing.value == true) {
                    _doChangePreviewMode(false);
                  } else {
                    onCancel(context);
                  }
                },
              )
            : Container(width: 40),
        title: Center(
          child: Text(
            widget.showImageCrop == true
                ? widget.galleryDisplaySettings?.uiTexts.titleCrop ?? ''
                : isPreviewing.value == true
                    ? widget.galleryDisplaySettings?.uiTexts.preview ?? ''
                    : widget.galleryDisplaySettings?.uiTexts.titleGallery ?? '',
            style: TextStyle(
              fontSize: 16,
              color: isPreviewing.value == true ? Colors.white : Colors.black,
              fontWeight: FontWeight.bold,
            ),
          ),
        ),
        // trailing: isPreviewing.value == true
        //     ? SvgPicture.asset(
        //         'packages/image_picker_plus_nic/assets/selecting.svg',
        //         fit: BoxFit.scaleDown,
        //         width: 24,
        //         height: 24)
        //     : Container(width: 40),
        trailing:  IconButton(
          iconSize: 40,
          icon: SvgPicture.asset(
            'packages/image_picker_plus_nic/assets/submit.svg',
            width: 24,
            height: 24),
            onPressed: () {
              onDone();
          },
        ),
      ),
    );
  }

  Widget _buildView(BuildContext context) {
    return noImages
        ? const Center(
            child: Text(
              'no image found',
              style: TextStyle(fontSize: 20, fontWeight: FontWeight.bold),
            ),
          )
        : buildGridView();
  }

  ValueListenableBuilder<bool> buildGridView() {
    return ValueListenableBuilder(
      valueListenable: isImagesReady,
      builder: (context, bool isImagesReadyValue, child) {
        if (isImagesReadyValue) {
          return ValueListenableBuilder(
            valueListenable: _mediaList,
            builder: (context, List<FutureBuilder<Uint8List?>> mediaListValue,
                child) {
              //print('mediaListValue=$mediaListValue');
              if (widget.showImageCrop) {
                return cropView(mediaListValue, 0, 0);
              } else if (widget.showImagePreview) {
                return ValueListenableBuilder(
                    valueListenable: isPreviewing,
                    builder: (context, bool isPreviewingValue, child) {
                      if (isPreviewingValue) {
                        return previewingView(mediaListValue);
                      } else {
                        return previewView(mediaListValue, 0, 0);
                      }
                    });
              } else {
                return normalView(mediaListValue);
              }
            },
          );
        } else {
          return loadingWidget();
        }
      },
    );
  }

  // 載入中widget
  Widget loadingWidget() {
    return SingleChildScrollView(
      child: Column(
        children: [
          Shimmer.fromColors(
            baseColor: widget.appTheme.shimmerBaseColor,
            highlightColor: widget.appTheme.shimmerHighlightColor,
            child: Column(
              children: [
                if (widget.showImageCrop) ...[
                  Container(
                      color: const Color(0xff696969),
                      height: 360,
                      width: double.infinity),
                  const SizedBox(height: 15),
                ],
                Padding(
                  padding:
                      const EdgeInsets.symmetric(horizontal: 22, vertical: 15),
                  child: GridView.builder(
                    shrinkWrap: true,
                    //physics: const NeverScrollableScrollPhysics(),
                    primary: false,
                    gridDelegate: widget.gridDelegate,
                    itemBuilder: (context, index) {
                      return Container(
                          padding: const EdgeInsets.all(10),
                          color: const Color(0xffaaaaaa),
                          //color: Colors.amber,
                          width: double.infinity);
                    },
                    itemCount: widget.showImageCrop ? 4 : 32,
                  ),
                ),
              ],
            ),
          ),
        ],
      ),
    );
  }

  IconButton existButton() {
    return IconButton(
      icon: Icon(Icons.clear_rounded, color: widget.blackColor, size: 30),
      onPressed: () {
        onCancel(context);
      },
    );
  }

  // 取消
  void onCancel(BuildContext context) {
    Navigator.of(context).maybePop(null);
  }

  void toCamera() {
    //print('toCamera()');
    widget.next?.call();
  }

  // 完成
  void onDone() async {
    //print('onDone()');
    double aspect = expandImage.value ? 6 / 8 : 1.0;
    if (widget.multiSelectionMode.value && widget.multiSelection) {
      if (areaOfCropsKeys.value.length !=
          widget.multiSelectedImages.value.length) {
        // scaleOfCropsKeys.value.add(cropKey.value.currentState?.scale);
        // areaOfCropsKeys.value.add(cropKey.value.currentState?.area);
      } else {
        if (indexOfLatestImage != -1) {
          // scaleOfCropsKeys.value[indexOfLatestImage] =
          //     cropKey.value.currentState?.scale;
          // areaOfCropsKeys.value[indexOfLatestImage] =
          //     cropKey.value.currentState?.area;
        }
      }

      List<SelectedByte> selectedBytes = [];
      for (int i = 0; i < widget.multiSelectedImages.value.length; i++) {
        File currentImage = widget.multiSelectedImages.value[i];
        String path = currentImage.path;
        bool isThatVideo = path.contains("mp4", path.length - 5);
        // File? croppedImage = !isThatVideo && widget.cropImage
        //     ? await cropImage(currentImage, indexOfCropImage: i)
        //     : null;
        File image = currentImage;
        Uint8List byte = await image.readAsBytes();
        SelectedByte img = SelectedByte(
          isThatImage: !isThatVideo,
          selectedFile: image,
          selectedByte: byte,
          index: i,
        );
        selectedBytes.add(img);
      }
      if (selectedBytes.isNotEmpty) {
        SelectedImagesDetails details = SelectedImagesDetails(
          selectedFiles: selectedBytes,
          multiSelectionMode: true,
          aspectRatio: aspect,
        );
        if (!mounted) return;
        Navigator.of(context).maybePop(details);
      }
    } else {
      File? image = selectedImage.value;
      if (image == null) return;
      String path = image.path;

      bool isThatVideo = path.contains("mp4", path.length - 5);
      // File? croppedImage =
      //     !isThatVideo && widget.cropImage ? await cropImage(image) : null;
      File img = image;
      Uint8List byte = await img.readAsBytes();

      SelectedByte selectedByte = SelectedByte(
        isThatImage: !isThatVideo,
        selectedFile: img,
        selectedByte: byte,
        index: selectedIndex,
      );
      SelectedImagesDetails details = SelectedImagesDetails(
        multiSelectionMode: false,
        aspectRatio: aspect,
        selectedFiles: [selectedByte],
      );
      if (!mounted) return;
      Navigator.of(context).maybePop(details);
    }
  }

  Widget doneButton() {
    return ValueListenableBuilder(
      valueListenable: indexOfSelectedImages,
      builder: (context, List<int> indexOfSelectedImagesValue, child) =>
          IconButton(
        icon: const Icon(Icons.arrow_forward_rounded,
            color: Colors.blue, size: 30),
        onPressed: () => onDone(),
      ),
    );
  }

  // 選擇圖片 grid view
  Widget normalGridView(List<FutureBuilder<Uint8List?>> mediaListValue,
      int currentPageValue, int lastPageValue) {
    return NotificationListener(
      onNotification: (ScrollNotification notification) {
        _handleScrollEvent(notification,
            currentPageValue: currentPageValue, lastPageValue: lastPageValue);
        return true;
      },
      child: GridView.builder(
        gridDelegate: widget.gridDelegate,
        itemBuilder: (context, index) {
          if (index == 0) {
            return Container(
              decoration: BoxDecoration(
                color: Colors.grey[300],
              ),
              margin: const EdgeInsets.all(5),
              child: InkWell(
                onTap: () => toCamera(),
                child: SvgPicture.asset(
                    'packages/image_picker_plus_nic/assets/camera.svg',
                    fit: BoxFit.scaleDown,
                    width: 24,
                    height: 24),
              ),
            );
          } else {
            return Padding(
              padding: const EdgeInsets.all(5),
              child: buildNormalImage(mediaListValue, index - 1),
            );
          }
        },
        itemCount: mediaListValue.length + 1,
      ),
    );
  }

  // 建立預覽中下面小圖示
  ValueListenableBuilder<File?> buildPreviewImage(
      List<FutureBuilder<Uint8List?>> mediaListValue,
      ValueNotifier<List<int>> indexOfSelectedImages,
      int index) {
    //print('buildPreviewImage(index=$index)');
    return ValueListenableBuilder(
      valueListenable: selectedImage,
      builder: (context, File? selectedImageValue, child) {
        //print('xxxxx selectedImageValue=$selectedImageValue');
        return ValueListenableBuilder(
          valueListenable: indexOfSelectedImages,
          builder: (context, List<int> indexOfSelectedImagesValue, child) {
            return ValueListenableBuilder(
              valueListenable: allImages,
              builder: (context, List<File?> allImagesValue, child) {
                //print(
                //    'indexOfSelectedImagesValue.length=${indexOfSelectedImagesValue.length}');
                //print(
                //    'indexOfSelectedImagesValue=${indexOfSelectedImagesValue}');
                int xx = indexOfSelectedImagesValue[index];
                //print('xx=$xx');
                FutureBuilder<Uint8List?> imageData = mediaListValue[xx];

                //print('imageData=${imageData}');
                File? imageFile = allImagesValue[xx];
                //print('xxxxx3 index=$index');
                if (imageFile != null) {
                  return Stack(
                    children: [
                      gesturePreviewDetector(imageFile, xx, imageData),
                      if (selectedImageValue == imageFile)
                        gesturePreviewDetector(
                            imageFile, xx, blurPreviewContainer()),
                    ],
                  );
                } else {
                  return Container();
                }
              },
            );
          },
        );
      },
    );
  }

  // 建立小圖示
  ValueListenableBuilder<File?> buildNormalImage(
      List<FutureBuilder<Uint8List?>> mediaListValue, int index) {
    //print('buildImage(index=$index)');
    return ValueListenableBuilder(
      valueListenable: selectedImage,
      builder: (context, File? selectedImageValue, child) {
        //print('xxxxx selectedImageValue=$selectedImageValue');
        return ValueListenableBuilder(
          valueListenable: allImages,
          builder: (context, List<File?> allImagesValue, child) {
            //print('xxxxx2 index=$index');
            return ValueListenableBuilder(
              valueListenable: widget.multiSelectedImages,
              builder: (context, List<File> selectedImagesValue, child) {
                FutureBuilder<Uint8List?> mediaList = mediaListValue[index];
                File? image = allImagesValue[index];
                //print('xxxxx3 index=$index');
                if (image != null) {
                  bool imageSelected = selectedImagesValue.contains(image);
                  //print('imageSelected=$imageSelected');
                  List<File> multiImages = selectedImagesValue;
                  //print('selectedImageValue=$selectedImageValue');
                  return Stack(
                    children: [
                      gestureDetector(image, index, mediaList),
                      if (widget.multiSelection == true) ...[
                        MultiSelectionWidget(
                          multiSelectionMode: widget.multiSelectionMode,
                          imageSelected: imageSelected,
                          multiSelectedImage: multiImages,
                          maximumSelection: widget.maximumSelection,
                        ),
                      ] else ...[
                        if (selectedImageValue == image)
                          gestureDetector(image, index, blurContainer()),
                      ]
                    ],
                  );
                } else {
                  return Container();
                }
              },
            );
          },
        );
      },
    );
  }

  // 選中的View
  Container blurContainer() {
    return Container(
      width: double.infinity,
      color: const Color(0x88333333),
      height: double.maxFinite,
      child: ClipRRect(
        borderRadius: BorderRadius.circular(6.0),
        child: SvgPicture.asset(
            'packages/image_picker_plus_nic/assets/selecting.svg',
            fit: BoxFit.scaleDown,
            width: 64,
            height: 64),
      ),
    );
  }

  Container blurPreviewContainer() {
    return Container(
      decoration: BoxDecoration(
        borderRadius: const BorderRadius.all(
          Radius.circular(6),
        ),
        color: Colors.transparent,
        border: Border.all(width: 2, color: const Color(0xff1FC97B)),
      ),
      width: 66,
      height: 66,
    );
  }

  // preview點擊偵測
  Widget gesturePreviewDetector(File imageFile, int index, Widget childWidget) {
    // print(
    //     'gesturePreviewDetector(imageFile=$imageFile, index=$index, childWidget=$childWidget)');
    return GestureDetector(
      onTap: () {
        //print('onTap()');
        onTapPreviewImage(imageFile, index);
      },
      child: ClipRRect(
        borderRadius: BorderRadius.circular(6.0),
        child: childWidget,
      ),
    );
  }

  // 點擊偵測
  Widget gestureDetector(File image, int index, Widget childWidget) {
    return ValueListenableBuilder(
      valueListenable: widget.multiSelectionMode,
      builder: (context, bool multipleValue, child) => ValueListenableBuilder(
        valueListenable: widget.multiSelectedImages,
        builder: (context, List<File> selectedImagesValue, child) =>
            GestureDetector(
          onTap: () {
            //print('onTap()');
            if (widget.multiSelectionMode.value == true) {
              onMultiSelectImage(image, selectedImagesValue, index);
            } else {
              onTapImage(image, selectedImagesValue, index);
            }
          },
          child: ClipRRect(
            borderRadius: BorderRadius.circular(4.0),
            child: childWidget,
          ),
        ),
      ),
    );
  }

  onMultiSelectImage(File image, List<File> selectedImagesValue, index) {
    //print('onMultiSelectImage()');
    //if (multipleValue) {
    selectionImageCheck(image, selectedImagesValue, index, enableCopy: true);
    //expandImageView.value = false;
    //moveAwayHeight.value = 0;

    //enableVerticalTapping.value = false;
    //setState(() => noPaddingForGridView = true);
  }

  // 小圖示點擊事件
  onTapImage(File image, List<File> selectedImagesValue, int index) {
    // print(
    //     'onTapImage(image=$image, selectedImagesValue=$selectedImagesValue, index=$index)');
    setState(() {
      if (widget.multiSelectionMode.value) {
        bool close = selectionImageCheck(image, selectedImagesValue, index);
        //print('close=$close');
        if (close) return;
      }
      selectedImage.value = image;
      selectedIndex = index;
      expandImageView.value = false;
      moveAwayHeight.value = 0;
      enableVerticalTapping.value = false;
      noPaddingForGridView = true;
    });
    if (!widget.cropImage) {
      onDone();
    }
  }

  // 小圖示點擊事件
  onTapPreviewImage(File imageFile, int index) {
    setState(() {
      selectedImage.value = imageFile;
      selectedIndex = index;
      expandImageView.value = false;
      moveAwayHeight.value = 0;
      enableVerticalTapping.value = false;
      noPaddingForGridView = true;
    });
  }

  bool selectionImageCheck(
      File image, List<File> multiSelectionValue, int index,
      {bool enableCopy = false}) {
    // print(
    //     "selectionImageCheck(index=$index, multiSelectionValue=$multiSelectionValue enableCopy=$enableCopy)");
    // print(
    //     'multiSelectionValue.contains(image)=${multiSelectionValue.contains(image)}');
    // print('selectedImage.value == image ${selectedImage.value == image}');

    if (multiSelectionValue.contains(image)) {
      // print('xxxxxxx multiSelectionValue.length=${multiSelectionValue.length}');
      // print('indexOfSelectedImages.value=${indexOfSelectedImages.value}');
      setState(() {
        int indexOfImage =
            multiSelectionValue.indexWhere((element) => element == image);
        multiSelectionValue.removeAt(indexOfImage);
        if (multiSelectionValue.isNotEmpty &&
            indexOfImage < scaleOfCropsKeys.value.length) {
          scaleOfCropsKeys.value.removeAt(indexOfImage);
          areaOfCropsKeys.value.removeAt(indexOfImage);
          indexOfLatestImage = -1;
        }
        if (indexOfSelectedImages.value.contains(index)) {
          indexOfSelectedImages.value.remove(index);
        }
      });
      //print('indexOfSelectedImages.value=${indexOfSelectedImages.value}');
      return true;
    } else {
      //print(
      //    'ooooooooo multiSelectionValue.length=${multiSelectionValue.length}');
      //print('indexOfSelectedImages.value=${indexOfSelectedImages.value}');
      if (multiSelectionValue.length < widget.maximumSelection) {
        //print('can select');
        setState(() {
          if (!multiSelectionValue.contains(image)) {
            //print('not contains');
            multiSelectionValue.add(image);
            if (multiSelectionValue.isNotEmpty) {
              scaleOfCropsKeys.value.add(cropKey.value.currentState?.scale);
              areaOfCropsKeys.value.add(cropKey.value.currentState?.area);
              if (!indexOfSelectedImages.value.contains(index)) {
                indexOfSelectedImages.value.add(index);
              }
            }
          } else if (areaOfCropsKeys.value.length !=
              multiSelectionValue.length) {
            //print('!!!!!!!');
            scaleOfCropsKeys.value.add(cropKey.value.currentState?.scale);
            areaOfCropsKeys.value.add(cropKey.value.currentState?.area);
          }
          if (widget.showImagePreview && multiSelectionValue.contains(image)) {
            //print('zzzzzzz');
            int index1 =
                multiSelectionValue.indexWhere((element) => element == image);
            if (indexOfLatestImage != -1) {
              scaleOfCropsKeys.value[indexOfLatestImage] =
                  cropKey.value.currentState?.scale;
              areaOfCropsKeys.value[indexOfLatestImage] =
                  cropKey.value.currentState?.area;
            }
            indexOfLatestImage = index1;
            if (!indexOfSelectedImages.value.contains(index)) {
              indexOfSelectedImages.value.add(index);
            }
          }

          if (enableCopy) selectedImage.value = image;
        });
      }
      //print('indexOfSelectedImages.value=${indexOfSelectedImages.value}');
      return false;
    }
  }

  Future<File?> cropImage(File imageFile, {int? indexOfCropImage}) async {
    await ImageCrop.requestPermissions();
    final double? scale;
    final Rect? area;
    if (indexOfCropImage == null) {
      scale = cropKey.value.currentState?.scale;
      area = cropKey.value.currentState?.area;
    } else {
      scale = scaleOfCropsKeys.value[indexOfCropImage];
      area = areaOfCropsKeys.value[indexOfCropImage];
    }

    if (area == null || scale == null) return null;

    final sample = await ImageCrop.sampleImage(
      file: imageFile,
      preferredSize: (2000 / scale).round(),
    );

    final File file = await ImageCrop.cropImage(
      file: sample,
      area: area,
    );
    sample.delete();
    return file;
  }

  void clearMultiImages() {
    setState(() {
      widget.multiSelectedImages.value = [];
      widget.clearMultiImages();
      indexOfSelectedImages.value.clear();
      scaleOfCropsKeys.value.clear();
      areaOfCropsKeys.value.clear();
    });
  }

  // 裁切頁
  Widget cropView(List<FutureBuilder<Uint8List?>> mediaListValue,
      int currentPageValue, int lastPageValue) {
    return ValueListenableBuilder(
      valueListenable: expandHeight,
      builder: (context, double expandedHeightValue, child) {
        return ValueListenableBuilder(
          valueListenable: moveAwayHeight,
          builder: (context, double moveAwayHeightValue, child) =>
              ValueListenableBuilder(
            valueListenable: expandImageView,
            builder: (context, bool expandImageValue, child) {
              double a = expandedHeightValue - 360;
              double expandHeightV = a < 0 ? a : 0;
              double moveAwayHeightV =
                  moveAwayHeightValue < 360 ? moveAwayHeightValue * -1 : -360;
              double topPosition =
                  expandImageValue ? expandHeightV : moveAwayHeightV;
              enableVerticalTapping.value = !(topPosition == 0);

              return Stack(
                alignment: AlignmentDirectional.topCenter,
                children: [
                  Column(
                    children: [
                      CropImageView(
                        cropKey: cropKey,
                        indexOfSelectedImages: indexOfSelectedImages,
                        selectedImage: selectedImage,
                        appTheme: widget.appTheme,
                        multiSelectionMode: widget.multiSelectionMode,
                        enableVerticalTapping: enableVerticalTapping,
                        expandHeight: expandHeight,
                        expandImage: expandImage,
                        expandImageView: expandImageView,
                        noDuration: noDuration,
                        clearMultiImages: clearMultiImages,
                        topPosition: topPosition,
                        whiteColor: widget.whiteColor,
                      ),
                      Padding(
                        padding: const EdgeInsets.only(top: 20),
                        child: SizedBox(
                          height: 64,
                          child: ListView.builder(
                            scrollDirection: Axis.horizontal,
                            //controller: scrollController,
                            itemCount: mediaListValue.length,
                            //itemExtent: 50,
                            itemBuilder: (context, index) {
                              return Container(
                                //color: Colors.amber,
                                padding: const EdgeInsets.symmetric(
                                    horizontal: 4, vertical: 4),
                                width: 64,
                                height: 64,
                                child: buildNormalImage(mediaListValue, index),
                              );
                              //return buildImage(mediaListValue, index);
                            },
                          ),
                        ),
                      ),
                    ],
                  ),
                  // ok按鈕
                  Positioned(
                    bottom: 30,
                    child: Center(
                      child: SizedBox(
                        width: MediaQuery.of(context).size.width - 74,
                        height: 60,
                        child: ElevatedButton(
                          style: ElevatedButton.styleFrom(
                            backgroundColor:
                                const Color(0xff1fc97b), // Background color
                          ),
                          onPressed: () async {
                            //print('onPressed()');
                            onDone();
                          },
                          child: Text(
                            widget.uiTexts.ok,
                            style: const TextStyle(
                              fontSize: 16,
                              fontWeight: FontWeight.bold,
                              color: Colors.white,
                            ),
                          ),
                        ),
                      ),
                    ),
                  ),
                ],
              );
            },
          ),
        );
      },
    );
  }

  // 預覽一般頁
  Widget previewView(List<FutureBuilder<Uint8List?>> mediaListValue,
      int currentPageValue, int lastPageValue) {
    //print('xxxx previewView()');
    return Column(
      mainAxisSize: MainAxisSize.min,
      children: [
        _buildTitle(context),
        Flexible(
          child: Padding(
            padding: const EdgeInsets.symmetric(horizontal: 22, vertical: 5),
            child: normalGridView(
              mediaListValue,
              0,
              0,
            ),
          ),
        ),
        //底部選單
        Row(
          mainAxisAlignment: MainAxisAlignment.center,
          children: [
            // TextButton(
            //   onPressed: () {
            //     _doChangePreviewMode(true);
            //   },
            //   child: Text(
            //     widget.uiTexts.preview,
            //     style: const TextStyle(
            //       fontSize: 14,
            //       fontWeight: FontWeight.w700,
            //       color: Color(0xff1fc97b),
            //     ),
            //   ),
            // ),
            Text(
              widget.uiTexts.multiPreview.format([
                widget.multiSelectedImages.value.length,
              ]),
              style: const TextStyle(
                fontSize: 16,
                fontWeight: FontWeight.w700,
                color: Colors.black,
              ),
            ),
            // IconButton(
            //   iconSize: 40,
            //   icon: SvgPicture.asset(
            //       'packages/image_picker_plus_nic/assets/submit.svg',
            //       width: 24,
            //       height: 24),
            //   onPressed: () {
            //     onDone();
            //   },
            // ),
          ],
        ),
      ],
    );
  }

  // 預覽中頁面
  Widget previewingView(List<FutureBuilder<Uint8List?>> mediaListValue) {
    double topPosition = 0;
    var screenSize = MediaQuery.of(context).size;
    return Container(
      color: Colors.black,
      child: Stack(
        alignment: AlignmentDirectional.topCenter,
        children: [
          Column(
            crossAxisAlignment: CrossAxisAlignment.start,
            children: [
              _buildTitle(context),
              PreviewImageView(
                cropKey: cropKey,
                indexOfSelectedImages: indexOfSelectedImages,
                selectedImage: selectedImage,
                appTheme: widget.appTheme,
                multiSelectionMode: widget.multiSelectionMode,
                enableVerticalTapping: enableVerticalTapping,
                expandHeight: expandHeight,
                expandImage: expandImage,
                expandImageView: expandImageView,
                noDuration: noDuration,
                clearMultiImages: clearMultiImages,
                topPosition: topPosition,
                whiteColor: widget.whiteColor,
              ),
            ],
          ),
          // 小圖片清單
          Positioned(
            bottom: 20,
            left: 10,
            child: Container(
              padding: const EdgeInsets.only(top: 20),
              child: SizedBox(
                height: 60,
                width: screenSize.width - 75,
                child: ListView.builder(
                  scrollDirection: Axis.horizontal,
                  itemCount: indexOfSelectedImages
                      .value.length, //mediaListValue.length,
                  itemBuilder: (context, index) {
                    return Container(
                      //color: Colors.amber,
                      padding: const EdgeInsets.symmetric(
                          horizontal: 4, vertical: 4),
                      width: 60,
                      height: 60,
                      child: buildPreviewImage(
                          mediaListValue, indexOfSelectedImages, index),
                    );
                  },
                ),
              ),
            ),
          ),
          // 送出按鈕
          Positioned(
            bottom: 25,
            right: 10,
            child: Center(
              child: badges.Badge(
                showBadge: true,
                // onTap: () {
                //   onDone();
                // },
                badgeContent: Text(
                  '${indexOfSelectedImages.value.length}',
                  style: const TextStyle(
                    fontSize: 12,
                    color: Colors.white,
                  ),
                ),
                badgeStyle: badges.BadgeStyle(
                  shape: badges.BadgeShape.circle,
                  badgeColor: widget.primaryColor,
                  padding: EdgeInsets.all(6),
                  //borderSide: BorderSide(color: Color(0xff6443FF), width: 1),
                  elevation: 0,
                ),
                child: SizedBox(
                  width: 50,
                  height: 50,
                  child: ElevatedButton(
                    style: ElevatedButton.styleFrom(
                      backgroundColor:
                          const Color(0xff1fc97b), // Background color
                    ),
                    onPressed: () async {
                      //print('onPressed()');
                      onDone();
                    },
                    child: SvgPicture.asset(
                      'packages/image_picker_plus_nic/assets/submit-white.svg',
                      width: 24,
                      height: 24,
                    ),
                  ),
                ),
                // child: Container(
                //   width: 54,
                //   height: 54,
                //   decoration: BoxDecoration(
                //     color: const Color(0xff1fc97b),
                //     borderRadius: const BorderRadius.all(
                //       Radius.circular(4),
                //     ),
                //   ),
                //   child: SvgPicture.asset(
                //     'packages/image_picker_plus_nic/assets/submit-white.svg',
                //     width: 16,
                //     height: 16,
                //     fit: BoxFit.scaleDown,
                //   ),
                // ),
              ),
            ),
          ),
        ],
      ),
    );
  }

  // 一般頁
  Widget normalView(List<FutureBuilder<Uint8List?>> mediaListValue) {
    return Column(
      mainAxisSize: MainAxisSize.min,
      children: [
        Flexible(
          child: Padding(
            padding: const EdgeInsets.symmetric(horizontal: 22, vertical: 5),
            child: normalGridView(
              mediaListValue,
              0,
              0,
            ),
          ),
        ),
        // ok按鈕
        Container(
          margin: const EdgeInsets.symmetric(vertical: 12, horizontal: 20),
          width: MediaQuery.of(context).size.width - 40,
          height: 54,
          child: ElevatedButton(
            style: ElevatedButton.styleFrom(
              shape: RoundedRectangleBorder(
                borderRadius: BorderRadius.circular(9),
              ),
              backgroundColor: widget.primaryColor, // Background color
            ),
            onPressed: widget.multiSelectedImages.value.isNotEmpty
                ? () {
                    //print('onPressed()');
                    onDone();
                  }
                : null,
            child: Text(
              widget.uiTexts.multiOk.format([
                widget.multiSelectedImages.value.length,
                widget.maximumSelection
              ]),
              style: widget.textStyle,
            ),
          ),
        ),
      ],
    );
  }

  @override
  bool get wantKeepAlive => true;

  // 變更預覽模式
  _doChangePreviewMode(bool b) {
    //print('_doChangePreviewMode($b)');
    isPreviewing.value = b;
    if (b == true) {
      widget.doChangeMode?.call(DisplayMode.preview);
    } else {
      widget.doChangeMode?.call(DisplayMode.normal);
    }
  }
}
